﻿package com.oneko.publicidad {
	import flash.display.Sprite;
	import flash.display.Shape;
	import flash.display.Loader;
	import flash.events.MouseEvent;
	import flash.events.Event;
	import flash.events.ErrorEvent;
	import flash.events.HTTPStatusEvent;
	import flash.events.SecurityErrorEvent;
	import flash.events.IOErrorEvent;
	import flash.events.NetStatusEvent;
	import flash.events.TimerEvent;
	import flash.events.AsyncErrorEvent;
	import flash.net.URLLoader;
	import flash.net.URLRequest;
	import flash.net.navigateToURL;
	import flash.net.NetStream;
	import flash.net.NetConnection;
	import fl.transitions.Tween;
	import fl.transitions.TweenEvent;
 	import fl.transitions.easing.*;
	import flash.text.TextField;
	import flash.text.TextFieldAutoSize;
	import flash.text.TextFormat;
	import flash.media.Video;
	import flash.media.SoundTransform;
	import flash.utils.Timer;
	
	import com.vilau.utils.Efectos;
	import com.oneko.publicidad.PubliParser;
	import com.akamai.net.AkamaiEnhancedNetStream;
	import net.codebites.utils.wrap;
	
	public class PubliMask extends Sprite{
		public var enabled:Boolean;
		
		private var _x:Number;
		private var _y:Number;
		private var _width:Number;
		private var _height:Number;
		private var _url:String="";
		private var _quit:Boolean;
		private var _quitSeconds:Number;

		private var filename:String;
		private var status:Number;
		private var preAdData:Array;
		private var mascara:Sprite;
		private var PreadLoader:Loader;
		private var txtCerrarAd:TextField;
		private var conCerrarAd:Sprite;
		
		private var showPread:Tween;
		private var deletePread:Tween;
		private var moveQuit:Tween;
		
		public var video:Video;
		private var sound:SoundTransform;
		private var stream:NetStream;
		private var conexion:NetConnection;
		private var mainStream:AkamaiEnhancedNetStream;
		
		private var cronoPubli:Timer;
		private var cronoQuit:Timer;
		
		private var efectos:Efectos;
		
		public function set properties(props:Object):void{
			_x=props.PUBLI.x;
			_y=props.PUBLI.y;
			_height=props.PUBLI.height;
			_width=props.PUBLI.width;
			_url=props.PUBLI.url;
			_quit=props.PUBLI.quit;
			_quitSeconds=props.PUBLI.quitSeconds;
		}
		public function get properties():Object{
			return {x:_x,y:_y,width:_width,height:_height,url:_url,quit:_quit};
		}
		
		public function PubliMask(props:Object):void { 
			properties=props;
			trace("URL de publicidad: "+_url);
			efectos=new Efectos();
			if (_url=="" || _url==null){
				enabled=false;
				return;
			}else enabled=true;
			createAdMask();
		}
		
		private function createAdMask():void{
			trace("Añado mascara");
			mascara=new Sprite();
			with (mascara){
				x=0;
				y=-2;
				graphics.beginFill(0x000000,1);
				graphics.drawRect(0,0,_width,_height);
				graphics.endFill();
				visible=true;
			}
			mascara.alpha=0;
			addChild(mascara);
			setChildIndex(mascara,numChildren-1);
			addMaskEvents(mascara);
		}
		
		public function setUrl(url:String):void {
			this._url = url;
			if (null == url || "" == url){
				enabled=false;
			}else {
				enabled=true;
			}
		}
		
		public function prepareData(mStream:AkamaiEnhancedNetStream,fn:String):void{
			if (!enabled) return;
			mainStream=mStream;
			filename=fn;
			var ext:String=_url.substr(_url.length-4,4);
			switch (ext){
				case '.flv':
					preAdData['urlvideo']=_url;
					PreadFLVHandler();
				break;
				case '.swf':
					PreadSWFHandler(_url);
				break;
				default:
					var PreadDataLoader:URLLoader = new URLLoader();
					PreadDataLoader.addEventListener(Event.COMPLETE,PreadHandler);
					PreadDataLoader.addEventListener(SecurityErrorEvent.SECURITY_ERROR,errorHandler);
					PreadDataLoader.addEventListener(IOErrorEvent.IO_ERROR,errorHandler);
					PreadDataLoader.addEventListener(HTTPStatusEvent.HTTP_STATUS, statusHandler);
					try {
						PreadDataLoader.load(new URLRequest(_url));
					} catch (err:Error) {
						trace("Error al cargar la informacion publicitaria preRoll=> "+err.message);
					}
			}
		}
		
		private function addMaskEvents(mascara:Sprite){
			trace("Meto eventos con addMaskEvents");
			mascara.addEventListener(MouseEvent.CLICK,adMaskClickHandler);
		
		}
		private function adMaskClickHandler(evt:MouseEvent){
			trace("Ejecutando eventos de la mascara");
			var urlClick:URLRequest=new URLRequest(preAdData['urlclick']);
			try {
				trace("Abriendo click "+preAdData['urlclick']);
				navigateToURL(urlClick);
			} catch (e:Error) {
				trace("No se pudo contabilizar el click!");
			}			
		}
		private function preRoll(){
			//view.sendEvent(ViewEvent.STOP,'true');
			//view.removeEventListener(ViewEvent.PLAY,preRoll);

			/*if (_quit==true){
				showQuitButton(mascara);
			}*/
			showPread=new Tween(mascara, "alpha", None.easeIn, 0,  100, 0.5, true);
			showPread.addEventListener(TweenEvent.MOTION_FINISH,cargaSWF);
		}
		
		private function cargaSWF(evt:TweenEvent=null){
			trace("Mascara cargada");
//			var url:String="http://www.cristalab.com/files/ejemplos/accordion/accordion.swf";
			var url:String=preAdData['urlvideo'];
			//var url="http://ads.eitb.com/2/es.eitb.com/home/1234567890@Right";
			//var url:String="http://10.126.2.25/multimedia/videos/2009/01/11/50164/barajas_cas_20090111_171004_logo_eitbcom_eskuma.flv";
			var urlRequest:URLRequest = new URLRequest(url); 
			PreadLoader= new Loader(); 
			var rect:Shape = new Shape();
			rect.graphics.beginFill(0x000000);
 			rect.graphics.drawRect(0, 0, mascara.width,mascara.height);
			rect.graphics.endFill();
			rect.x=0;
			rect.y=0;
			mascara.addChild(rect);
			PreadLoader.mask=rect;
			
			PreadLoader.load(urlRequest);
			PreadLoader.contentLoaderInfo.addEventListener(Event.COMPLETE, swfLoaded);
			PreadLoader.addEventListener(IOErrorEvent.IO_ERROR,cargaSWFStatusHandler);
			
			PreadLoader.contentLoaderInfo.addEventListener(Event.UNLOAD,swfUnloadHandler);
			PreadLoader.addEventListener(Event.UNLOAD,swfUnloadHandler);
		}
		private function swfLoaded(evt:Event=null){
			trace("SWF cargado");
			var ldr:Loader=evt.target.loader;
			var tmp:Array=preAdData['tiempovideo'].split(":");
			preAdData['tiempovideo']=tmp[0]*60*60+tmp[1]*60+tmp[2];
			trace(preAdData['tiempovideo']);
			var cronoPubli:Timer=new Timer(preAdData['tiempovideo']*1000,1);
			cronoPubli.addEventListener(TimerEvent.TIMER, cronoPubliHandler);
            cronoPubli.start();
			
			ldr.visible=true;
			ldr.alpha=100;
			ldr.width=_width;
			ldr.height=_height;
			mascara.addChild(ldr);
			mascara.setChildIndex(ldr,mascara.numChildren-1);
			trace("Loader añadido");
			
			var mask:Sprite=new Sprite();
			with (mask){
				x=0;
				y=-2;
				graphics.beginFill(0x000000,1);
				graphics.drawRect(0,0,mascara.width,mascara.height);
				graphics.endFill();
				visible=true;
				alpha=0;
				buttonMode=true;
				useHandCursor=true;
			}
			addMaskEvents(mask);
			mascara.addChild(mask);
			mascara.setChildIndex(mask,mascara.numChildren-1);
			
			if (_quit){
				trace("Inicio mostrado de quit");
				showQuitButton(mascara,_quitSeconds);
			}
        }
		
		private function showQuitButton(where:Sprite, time:Number){
			trace("Timer para enseñar quit");
			cronoQuit=new Timer(time*1000,1);
			cronoQuit.addEventListener(TimerEvent.TIMER, wrap(cronoQuitHandler,where));
            cronoQuit.start();
		}
		
		private function crearTexto(datX:Number,datY:Number,nombre:String,formato:TextFormat=null){
			var tamanio=_height/30;
			if (formato==null){
				var formato = new TextFormat();
				with (formato){
					font = "Verdana";
					color = 0xFFFFFF;
					size = tamanio;
					underline = false;
				}
			}
			var txt= new TextField();
			with (txt){
				autoSize = TextFieldAutoSize.LEFT;
				background = false;
				border = false;
				multiline = false;
				x = datX;
				y = datY;
				defaultTextFormat = formato;
				name=nombre;
				selectable=false;
			}
			return txt;
		}
		
		private function deletePreAd(evt:MouseEvent=null){
			if (mascara!=null){
				if (PreadLoader!=null){
					PreadLoader.unload();
					PreadLoader=null;
				}
				if (stream!=null)
					stream.close();
				removeChild(mascara);
				mainStream.play(filename);
				//view.sendEvent('PLAY');
			}
			enabled=false;
		}
		
		private function PreadHandler(evt:Event=null):void{
			trace("Inicio preRoll");
			if (evt!=null){
				var ldrData=evt.target.data;
				preAdData=loaderHandler(ldrData);
			}
			if (preAdData['urlvideo']!=undefined && preAdData['urlvideo']!=''){
				var urlPing:URLRequest=new URLRequest(preAdData['urlpixel']);
				var ping = new URLLoader();
				ping.addEventListener(Event.COMPLETE,pingHandler);
				try {
					ping.load(urlPing);
				} catch (err:Error) {
					trace("Error al ejecutar el ping=> "+err.message);
				}
				var ext:String=preAdData['urlvideo'].substr(preAdData['urlvideo'].length-4,4);
				trace("Añado "+ext+" en preAdData");				
				switch (ext){
					case '.flv':
						//view.addViewListener(ViewEvent.PLAY,PreadFLVHandler);
						PreadFLVHandler();
					break;
					default:
						//view.addViewListener(ViewEvent.PLAY,preRoll);					
						preRoll();
				}
			}
		}
		
		private function loaderHandler(target){
			var error:String;
			try {
				var dat = XML(target);
			} catch (err:Error) {
				error = status+'Archivo XML no valido';
				trace(error);
				deletePreAd();
				return new Array('error');
			}
			var publidata:Array=PubliParser.parse(dat);
			if(publidata['urlvideo']== undefined) { 
				error = 'No se han encontrado datos publicitarios.';
				trace(error);
				deletePreAd();
				return new Array('error');
			}
			trace("PUBLIDATA:"+publidata['urlvideo']);
			return publidata;
		}
		
		private function PreadFLVHandler():void{
			showPread=new Tween(mascara, "alpha", None.easeIn, 0,  100, 0.5, true);
			showPread.addEventListener(TweenEvent.MOTION_FINISH,setVideo);
		}
		private function PreadSWFHandler(file:String):void{
			preAdData=new Array();
			preAdData['urlvideo']=file;
			PreadHandler(null);
		}
		private function pingHandler(evt:Event){};
		/** Catch security and io errors **/
		private function errorHandler(evt:ErrorEvent):void {
			trace("Error generico al cargar la informacion publicitaria; Estado HTTP:"+status+': '+evt.text);
		};
		/** Save the http status **/
		private function statusHandler(evt:HTTPStatusEvent):void {
			status = evt.status;
		};
		
		private function setVideo(evt:TweenEvent){
			trace("Reproduzco el video");
			conexion = new NetConnection();
			conexion.connect(null);
			
			stream = new NetStream(conexion);
			stream.checkPolicyFile = true;
			stream.addEventListener(NetStatusEvent.NET_STATUS, streamHandler); 
			stream.addEventListener(IOErrorEvent.IO_ERROR,errorHandler);
			stream.addEventListener(AsyncErrorEvent.ASYNC_ERROR,errorHandler);
			stream.bufferTime = 3;
			
			video = new Video();
			video.height = _height;
			video.width = _width;
			video.x = 0;
			video.y = 0;
			
			var obj:Object = new Object();
			stream.client = obj;
			obj.onMetaData = this.MetaData;
			video.attachNetStream(stream);

			sound = new SoundTransform();
			stream.soundTransform = sound;
			
			mascara.addChild(video);
			mascara.setChildIndex(video,mascara.numChildren-1);
			
			if (_quit){
				trace("Inicio mostrado de quit");
				showQuitButton(mascara,_quitSeconds);
			}
			trace("URL del video"+preAdData['urlvideo']);
			
			stream.play(preAdData['urlvideo'].toString());
			enabled=false;
		}
		
		private function setSize(w:Number,h:Number):void{
			_width=w;
			_height=h;
		}
		
		public function resize(sW:Number,sH:Number):void{
			setSize(sW,sH);
			trace("Resizeando");
			if (mascara!=null){
				with (mascara){
					graphics.beginFill(0x000000,1);
					graphics.drawRect(0,0,_width,_height);
					graphics.endFill();
					visible=true;
				}
			}
			
			if (video!=null){
				video.width=_width;
				video.height=_height;
			}
			
			if (conCerrarAd!=null){
				conCerrarAd.x=_width-conCerrarAd.width-2;
				conCerrarAd.y=_height-conCerrarAd.height-5;
				var formato:TextFormat=txtCerrarAd.getTextFormat();
				formato.size=_height/28;
				txtCerrarAd.setTextFormat(formato);
			}
		}

		private function MetaData(info:Object) {
			trace(info);
		}

		private function streamHandler(evt:NetStatusEvent){
			trace(evt.info.code);
			if (evt.info.code=="NetStream.Play.Stop"){
				trace("Video acabado, cerrando publi");
				stream.close();
				this.deletePreAd();			
			}
		}
		private function cargaSWFStatusHandler(evt:IOErrorEvent){
			trace("Error cargando el SWF=>"+evt.text);
		}
		
		public function cronoPubliHandler(event:TimerEvent):void {
			trace("Video acabado, cerrando publi");
			this.deletePreAd();			
        }
		
		private function swfUnloadHandler(evt:Event):void{
			trace("Descargando swf");
			if (cronoQuit!=null)
				cronoQuit.stop();
			if (cronoPubli!=null)
				cronoPubli.stop();
			
			PreadLoader.mask=null;
			PreadLoader.contentLoaderInfo.removeEventListener(Event.COMPLETE, swfLoaded);
			PreadLoader.removeEventListener(IOErrorEvent.IO_ERROR,cargaSWFStatusHandler);
			PreadLoader.contentLoaderInfo.removeEventListener(Event.UNLOAD,swfUnloadHandler);
			PreadLoader=null;
			trace("Swf descargado");
		}
		
		private function cronoQuitHandler(where:Sprite,event:TimerEvent=null):void {
			trace("Mostrando quit");
			conCerrarAd=new Sprite();
			conCerrarAd.graphics.beginFill(0x666666,0.5);
			conCerrarAd.graphics.lineStyle(1, 0xCECECE);
			conCerrarAd.graphics.drawRoundRect(0, 0, 100, 20,5);
			conCerrarAd.graphics.endFill();
			conCerrarAd.buttonMode=true;
			conCerrarAd.mouseChildren=false;
			conCerrarAd.alpha=0.2;
			
			var tamanio=_height/28;
			var formato = new TextFormat();
			with (formato){
				font = "Verdana";
				color = 0xFFFFFF;
				size = tamanio;
				bold = true;
			}
				
			txtCerrarAd=crearTexto(0,0,'txtCerrarAd',formato);
			
			txtCerrarAd.text="CERRAR";
			txtCerrarAd.x=5;
			txtCerrarAd.y=2;
			
			conCerrarAd.addEventListener(MouseEvent.CLICK,deletePreAd);
			
			where.addChild(conCerrarAd);
			where.setChildIndex(conCerrarAd,where.numChildren-1);
			conCerrarAd.x=where.width-conCerrarAd.width-2;
			conCerrarAd.addChild(txtCerrarAd);
			moveQuit=efectos.moveTo(conCerrarAd,"up",conCerrarAd.width,where.height,where.height-conCerrarAd.height-5);
		}
		
	}
	
}